﻿using System;
using System.Web.Mvc;
using MvcFlow.Diagnostics;

namespace MvcFlow
{
    [AttributeUsage(AttributeTargets.Class | AttributeTargets.Method)]
    public class WorkflowRedirectAttribute : ActionFilterAttribute
    {
        private static readonly ILog log = LogManager.GetLog("WorkflowRedirectAttribute");
        private readonly string workflowName;

        public override void OnActionExecuted(ActionExecutedContext filterContext)
        {
            if ( filterContext.Result is RedirectResult || filterContext.Result is RedirectToRouteResult)
            {
                // We resolve the workflow runtime directly, since we do not want to depend on a specific IOC container implementation
                // e.g Autofac being able to do property injection on action filters.
                var workflowRuntime = DependencyResolver.Current.GetService<IWorkflowRuntime>();
               
                // We have to force synchronous execution since MVC4 still does not support TPL based action filters.
                var workflowTask = workflowRuntime.ExecuteStep(filterContext.RequestContext, workflowName);
                workflowTask.Wait();

                var newResult = workflowTask.Result.Bind(filterContext.Controller);

                if ( newResult is RedirectResult || newResult is RedirectToRouteResult)
                {
                    filterContext.Result = newResult;
                }
                else
                {
                    log.Error("Worfklow {0} did not provide a redirect result",workflowName);
                }
            }
            else
            {
                log.Info("Action {0} on controller {1} did not redirect, workflow not triggered",filterContext.ActionDescriptor.ActionName,filterContext.ActionDescriptor.ControllerDescriptor.ControllerName);
            }
        }

        public WorkflowRedirectAttribute(string workflowName)
        {
            this.workflowName = workflowName;
        }
    }
}